package com.hlkj.baojin.service.impl;

import com.google.common.collect.Lists;
import com.hlkj.baojin.constant.BaojinConstant;
import com.hlkj.baojin.dao.IAlarmRecordDao;
import com.hlkj.baojin.dao.IEarlyAlarmRecordDao;
import com.hlkj.baojin.dao.repository.AlarmRecordRepository;
import com.hlkj.baojin.dao.repository.EarlyAlarmRecordRepository;
import com.hlkj.baojin.dao.repository.RealDataRepository;
import com.hlkj.baojin.entity.AlarmRecord;
import com.hlkj.baojin.entity.DeviceStatusDataLog;
import com.hlkj.baojin.entity.EarlyAlarmRecord;
import com.hlkj.baojin.entity.dto.*;
import com.hlkj.baojin.jwt.JwtUser;
import com.hlkj.baojin.service.*;
import com.hlkj.baojin.utils.ErrororUtil;
import com.hlkj.baojin.utils.bean.CopyUtil;
import com.hlkj.baojin.utils.bean.Page;
import org.apache.commons.lang3.time.FastDateFormat;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;

import java.util.*;

/**
 * @author 徐其伟
 * @Description:
 * @date 18-12-17 上午9:58
 */
@Service
public class AlarmRecordServiceImpl implements AlarmRecordService {
    @Value("${jwt.backstage.phone}")
    private String backStagePhone;
    @Autowired
    private IAlarmRecordDao alarmRecordDao;
    @Autowired
    private IEarlyAlarmRecordDao earlyAlarmRecordDao;
    @Autowired
    private AlarmRecordRepository alarmRecordRepository;
    @Autowired
    private IFileService fileService;
    @Autowired
    private CompanyService companyService;
    @Autowired
    private IRealDataService realDataService;
    @Autowired
    private DeviceService deviceService;
    @Autowired
    private IUserService userService;
    @Autowired
    private EarlyAlarmRecordRepository earlyAlarmRecordRepository;
    @Autowired
    private SmsService smsService;
    @Autowired
    private RealDataRepository realDataRepository;
    @Autowired
    private ICompanyAreaService companyAreaService;

    /**
     * 轮训短信发送
     */
    @Scheduled(cron = "0/30 * * * * ?")
    public void alarmSmsSend() {
        List<AlarmRecord> list = alarmRecordRepository.getNeedToSendSmsAlarms();
        for (AlarmRecord ar : list) {
            alarmRecordRepository.updateSmsAlarms(ar.getId());
            smsService.sendAlarmSms(ar, false);
        }
    }

    /** 添加报警接口 可调3个参数构造方法
     * @param alarmRecord
     */
    @Override
    public void addAlarmRecord(AlarmRecord alarmRecord)  {
        alarmRecord.setHandleStatus(0);
        alarmRecord.setAlarmStatus(0);
        alarmRecord.setDelete(BaojinConstant.IS_NO_DELETE);
        alarmRecord = alarmRecordDao.save(alarmRecord);
        //异步发送信息
        smsService.sendAlarmSms(alarmRecord, true);

    }

    /**预警添加 可调3个参数构造方法
     * @param alarmRecord
     */
    @Override
    public void addEarlyAlarmRecord(EarlyAlarmRecord alarmRecord) {
        alarmRecord.setCreateTime(System.currentTimeMillis());
        alarmRecord.setUpdateTime(System.currentTimeMillis());
        alarmRecord.setDelete(BaojinConstant.IS_NO_DELETE);
        alarmRecord = earlyAlarmRecordDao.save(alarmRecord);

        smsService.sendEarlyAlarmSms(alarmRecord, true);
    }

    /** 报警恢复
     * @param id
     * @param createTime
     */
    @Override
    public void recoverAlarm(String id, Long createTime){
        alarmRecordRepository.recoverAlarm(id,createTime);
    }

    /**
     * 是否能够添加报警记录 如果存在没有恢复时间报警记录 即不能添加
     * @param id
     * @return
     */
    @Override
    public boolean findByDevice(String id){
       return alarmRecordRepository.findByDevice(id);
    }

    @Override
    public ModelList<AlarmRecordDto> listAlarmRecord(AlarmSearch alarmSearch, Page page) {
        List<AlarmRecordDto> result = Lists.newArrayList();
        List<String> companyIds;
        String companyId = null;

        JwtUser currentUser = userService.getCurrentUser();
        if(currentUser.getType() == 2){
            companyIds = companyService.getIdsByNameLike(alarmSearch.getSearchMsg());
        }else{
            companyIds = Lists.newArrayList();
            companyId = currentUser.getDeptId();
        }
        List<String> deviceIds = deviceService.getIdsByNameAndItem(alarmSearch.getSearchMsg());

        ModelList<AlarmRecord> arm = alarmRecordRepository.listAlarmRecord(companyId, alarmSearch, companyIds, deviceIds, page);
        arm.getList().forEach(ar ->{
            result.add(getAlarmRecordDto(ar));
        });
          return new ModelList(result, arm.getCount());
    }

    @Override
    public AlarmRecordDto getAlarmRecord(String id){
        AlarmRecord alarmRecord = alarmRecordDao.findById(id).get();
        return getAlarmRecordDto(alarmRecord);
    }

    private AlarmRecordDto getAlarmRecordDto(AlarmRecord ar) {
        AlarmRecordDto arDto = CopyUtil.copy(ar, AlarmRecordDto.class);
        CompanyDto company = companyService.findCompanyById(arDto.getCompanyId());
        DeviceDto device = deviceService.findDeviceById(arDto.getDeviceId());
        arDto.setLocation(companyAreaService.getCompanyAreaNameByCompanyAreaId(device.getCompanyArea()));
        arDto.setMonitorObject(device.getMonitorObject());
        arDto.setStoreItems(device.getMonitorArticle());
        arDto.setCompanyName(company.getName());
        arDto.setLegalPerson(company.getLegalPerson());
        arDto.setLegalPersonPhone(company.getLegalPersonPhone());
        arDto.setCompanyPrincipal(company.getCompanyPrincipal());
        arDto.setCompanyPrincipalPhone(company.getCompanyPrincipalPhone());
        arDto.setControlMan(company.getCenterControlPrincipal());
        arDto.setControlTelephone(company.getCenterControlAttendancePhone());
        arDto.setControlManMobilePhone(company.getCenterControlPrincipalPhone());
        arDto.setMonitorType(device.getMonitorType());
        arDto.setTechManual(device.getTechManual());
        arDto.setEmergencyPlan(device.getEmergencyPlan());
        AlarmReason alarmReason = arDto.getAlarmReason();
        HandleMethod handleMethod = arDto.getHandleMethod();
        if(alarmReason != null && alarmReason.getAlarmFile() != null) {
            alarmReason.setAlarmFile(fileService.getFileLocalhost(alarmReason.getAlarmFile()));
        }
        if(handleMethod != null && handleMethod.getHandleMethodFile() != null) {
            handleMethod.setHandleMethodFile(fileService.getFileLocalhost(handleMethod.getHandleMethodFile()));
        }
        if(handleMethod != null && handleMethod.getHandleResultFile() != null) {
            handleMethod.setHandleResultFile(fileService.getFileLocalhost(handleMethod.getHandleResultFile()));
        }
        return arDto;
    }

    @Override
    public ModelList<EarlyAlarmRecordDto> listEarlyAlarmRecord(AlarmSearch alarmSearch, Page page) {
        List<String> companyIds;
        String companyId = null;

        JwtUser currentUser = userService.getCurrentUser();
        if(currentUser.getType() == 2){
            companyIds = companyService.getIdsByNameLike(alarmSearch.getSearchMsg());
        }else{
            companyIds = Lists.newArrayList();
            companyId = currentUser.getDeptId();
        }
        List<String> deviceIds = deviceService.getIdsByNameAndItem(alarmSearch.getSearchMsg());

        ModelList<EarlyAlarmRecord> arm = earlyAlarmRecordRepository.listEarlyAlarmRecord(companyId, alarmSearch, companyIds, deviceIds, page);
        List<EarlyAlarmRecordDto> result = Lists.newArrayList();
        arm.getList().forEach(ar ->{
            result.add(getEarlyAlarmDto(ar));
        });
        return new ModelList<>(result, arm.getCount());
    }

    @Override
    public EarlyAlarmRecordDto getEarlyAlarm(String id){
        return getEarlyAlarmDto(earlyAlarmRecordDao.findById(id).get());
    }

    private EarlyAlarmRecordDto getEarlyAlarmDto(EarlyAlarmRecord ar) {
        EarlyAlarmRecordDto dto = CopyUtil.copy(ar, EarlyAlarmRecordDto.class);
        CompanyDto company = companyService.findCompanyById(ar.getCompanyId());
        DeviceDto device = deviceService.findDeviceById(ar.getDeviceId());
        dto.setLocation(companyAreaService.getCompanyAreaNameByCompanyAreaId(device.getCompanyArea()));
        dto.setMonitorObject(device.getMonitorObject());
        dto.setStoreItems(device.getMonitorArticle());
        dto.setCompanyName(company.getName());
        dto.setMonitorType(device.getMonitorType());
        dto.setLegalPerson(company.getLegalPerson());
        dto.setLegalPersonPhone(company.getLegalPersonPhone());
        dto.setCompanyPrincipal(company.getCompanyPrincipal());
        dto.setCompanyPrincipalPhone(company.getCompanyPrincipalPhone());
        dto.setControlMan(company.getCenterControlPrincipal());
        dto.setControlTelephone(company.getCenterControlAttendancePhone());
        dto.setControlManMobilePhone(company.getCenterControlPrincipalPhone());
        dto.setTechManual(device.getTechManual());
        dto.setEmergencyPlan(device.getEmergencyPlan());
        return dto;
    }

    @Override
    public void commitAlarm(String id, AlarmReason alarmReason) {
        AlarmRecord alarmRecord = alarmRecordDao.findById(id).orElse(null);
        ErrororUtil.isTrueNull(alarmRecord, "上报报警", "id不存在");
        alarmRecord.setAlarmReason(alarmReason);
        alarmRecord.setAlarmStatus(1);
        alarmRecordDao.save(alarmRecord);
    }

    @Override
    public void commitHandle(String id, HandleMethod handleMethod) {
        AlarmRecord alarmRecord = alarmRecordDao.findById(id).orElse(null);
        ErrororUtil.isTrueNull(alarmRecord, "上报处理结果", "id不存在");
        alarmRecord.setHandleMethod(handleMethod);
        alarmRecord.setHandleStatus(1);
        alarmRecordDao.save(alarmRecord);
    }

    @Override
    public StatusDataVO alarmWaveMsg(String id) {
        AlarmRecord alarmRecord = alarmRecordDao.findById(id).get();
        DeviceDto device = deviceService.findDeviceById(alarmRecord.getDeviceId());
        Long endTime = alarmRecord.getRecoverTime();
        Double max = 0D;

        if(alarmRecord.getRecoverTime() == null){
            alarmRecord.setRecoverTime(System.currentTimeMillis());
        }
        Map<String, StatusDataLog> dataList = new TreeMap<>();
        List<DeviceStatusDataLog> logList = realDataRepository.getAlarmWaveMsg(alarmRecord.getDeviceId(), alarmRecord.getCreateTime(), alarmRecord.getRecoverTime());
        //时间过滤
        for (DeviceStatusDataLog log : logList) {
            for (StatusDataLog statusDataLog : log.getDetails()) {
                if (statusDataLog.getRealValue() != null) {
                    if (max < statusDataLog.getRealValue()) {
                        max = statusDataLog.getRealValue();
                    }
                    dataList.put(FastDateFormat.getInstance("yyyy/MM/dd HH:mm:ss").format(new Date(statusDataLog.getRealTime()))
                            , new StatusDataLog(statusDataLog.getIsRecover(), statusDataLog.getRealValue()));
                }
            }
        }
        //断开连接时候填入空值
        realDataService.fault(dataList);
        StatusDataVO statusDataVO = new StatusDataVO(
                dataList.keySet(),
                dataList,
                device.getMonitorType(),
                device.getSafeValueDown(),
                device.getGetSafeValueUp()
        );

        statusDataVO.setStartTime(alarmRecord.getCreateTime());
        statusDataVO.setEndTime(endTime);
        statusDataVO.setMaxValue(max);
        return statusDataVO;
    }

    @Override
    public boolean findByDeviceEarly(String id) {
        return alarmRecordRepository.findByDeviceEarly(id);
    }

    @Override
    public void recoverEarlyAlarm(String id, long createTime) {
        alarmRecordRepository.recoverEarlyAlarm(id,createTime);
    }
}
